
#include <set>
#include <vector>
#include "procdure.h"
#include "page.h"
#include <algorithm>
#include <numeric>
#include <iostream>

using namespace std;

class memory_manage
{
private:
    // 系统时间
    int io_time;      // 系统的页面换入、换出时间
    int compute_time; // 系统的进程执行时间
    int group_time;   // 上一个组的完成时间
    // 虚拟空间和内存
    int total_size;    // 虚拟存储空间
    int memory;        // 内存容量
    int capacity;      // 内存页面容量
    int current_pages; // 内存当前页面数
    // vector<int> valid_page; // 内存中的页面
    //  页面
    int page_n;         // 页面总数
    int page_size;      // 页面大小
    vector<page> pages; // 所有页面
    // 进程
    int pro_n;                          // 进程数
    int finished_pro;                   // 最近刚完成的，不会再被用到的进程的序号
    vector<procdure> pros;              // 所有进程
    vector<pair<int, int>> visit_times; // 记录每个进程的 visit {start, end}
    vector<int> page_number;            // 当前进程所需的所有页的页号
    vector<int> pages_to_load;          // 当前进程需要加载进内存的页号
    vector<int> group_pros;             // 开始时间相同的进程为一组，并行计算
    vector<vector<int>> pro_pages;      // 存放每个进程所用到的所有页面
public:
    memory_manage(int L, int M, int N);
    ~memory_manage();

    void push_procdure(int a, int b, int c, int d); // 添加进程
    void set_page(vector<int> group);               // 设置页面大小、每个页面起始位置

    int select(int index);                 // 寻找要换出的页面（OPT）
    void release_finished_pages(int time); // 释放内存中time时刻已完成的页面

    void get_pages_to_load();            // 获得pages_to_loads
    vector<int> get_group(int &pro_idx); // 获得group_pros
    vector<int> get_numbers(int n);      // 返回第n个进程所需的所有页号

    void page_offload(int idx);     // 换出页面
    void off_print(vector<int> &x); // 打印输出
    void page_reload();             // 页面换入
    void pro_execute(int idx);      // 进程执行
    void run();                     // 模拟执行
};
